In [ ]:
Copied!
!pip install git+https://github.com/paulknysh/blackbox.git@master
!pip install git+https://github.com/paulknysh/blackbox.git@master
At time of this tutorial, blackbox not work with Python 3.10. Quick fix version until update
In [ ]:
Copied!
!pip install git+https://github.com/AwesomeTrading/blackbox.git@master
!pip install git+https://github.com/AwesomeTrading/blackbox.git@master
Sample strategy¶
In [1]:
Copied!
import talib.abstract as ta
from lettrade import DataFeed, Strategy, crossover, crossunder
from lettrade.exchange.backtest import ForexBackTestAccount, let_backtest
class SmaCross(Strategy):
ema1_period = 9
ema2_period = 21
def indicators(self, df: DataFeed):
df["ema1"] = ta.EMA(df, timeperiod=self.ema1_period)
df["ema2"] = ta.EMA(df, timeperiod=self.ema2_period)
df["signal_ema_crossover"] = crossover(df.ema1, df.ema2)
df["signal_ema_crossunder"] = crossunder(df.ema1, df.ema2)
def next(self, df: DataFeed):
if len(self.orders) > 0 or len(self.trades) > 0:
return
if df.signal_ema_crossover[-1]:
price = self.data.close[-1]
self.buy(size=0.1, sl=price - 0.001, tp=price + 0.001)
elif df.signal_ema_crossunder[-1]:
price = self.data.close[-1]
self.sell(size=0.1, sl=price + 0.001, tp=price - 0.001)
lt = let_backtest(
strategy=SmaCross,
datas="example/data/data/EURUSD_5m_0_10000.csv",
account=ForexBackTestAccount,
)
import talib.abstract as ta
from lettrade import DataFeed, Strategy, crossover, crossunder
from lettrade.exchange.backtest import ForexBackTestAccount, let_backtest
class SmaCross(Strategy):
ema1_period = 9
ema2_period = 21
def indicators(self, df: DataFeed):
df["ema1"] = ta.EMA(df, timeperiod=self.ema1_period)
df["ema2"] = ta.EMA(df, timeperiod=self.ema2_period)
df["signal_ema_crossover"] = crossover(df.ema1, df.ema2)
df["signal_ema_crossunder"] = crossunder(df.ema1, df.ema2)
def next(self, df: DataFeed):
if len(self.orders) > 0 or len(self.trades) > 0:
return
if df.signal_ema_crossover[-1]:
price = self.data.close[-1]
self.buy(size=0.1, sl=price - 0.001, tp=price + 0.001)
elif df.signal_ema_crossunder[-1]:
price = self.data.close[-1]
self.sell(size=0.1, sl=price + 0.001, tp=price - 0.001)
lt = let_backtest(
strategy=SmaCross,
datas="example/data/data/EURUSD_5m_0_10000.csv",
account=ForexBackTestAccount,
)
Run optimize¶
In [2]:
Copied!
import black_box as bb
def params_parser(args):
return [
("ema1_period", int(args[0])),
("ema2_period", int(args[1])),
]
def result_parser(result):
return result["equity"]
best_params = bb.search_min(
f=lt.optimize_model(
params_parser=params_parser,
result_parser=result_parser,
fork_data=True,
), # given function
domain=[[5, 25], [10, 50]], # ranges of each parameter
budget=200, # total number of function calls available
batch=12, # number of calls that will be evaluated in parallel
resfile="output.csv",
) # text file where results will be saved
import black_box as bb
def params_parser(args):
return [
("ema1_period", int(args[0])),
("ema2_period", int(args[1])),
]
def result_parser(result):
return result["equity"]
best_params = bb.search_min(
f=lt.optimize_model(
params_parser=params_parser,
result_parser=result_parser,
fork_data=True,
), # given function
domain=[[5, 25], [10, 50]], # ranges of each parameter
budget=200, # total number of function calls available
batch=12, # number of calls that will be evaluated in parallel
resfile="output.csv",
) # text file where results will be saved
[blackbox] FYI: budget was adjusted to be 204 [blackbox] evaluating batch 1/17 (samples 1..12/204) @ 2024-05-28 21:20:35 ... [blackbox] evaluating batch 2/17 (samples 13..24/204) @ 2024-05-28 21:20:35 ... [blackbox] evaluating batch 3/17 (samples 25..36/204) @ 2024-05-28 21:20:36 ... [blackbox] evaluating batch 4/17 (samples 37..48/204) @ 2024-05-28 21:20:36 ... [blackbox] evaluating batch 5/17 (samples 49..60/204) @ 2024-05-28 21:20:37 ... [blackbox] evaluating batch 6/17 (samples 61..72/204) @ 2024-05-28 21:20:37 ... [blackbox] evaluating batch 7/17 (samples 73..84/204) @ 2024-05-28 21:20:38 ... [blackbox] evaluating batch 8/17 (samples 85..96/204) @ 2024-05-28 21:20:38 ... [blackbox] evaluating batch 9/17 (samples 97..108/204) @ 2024-05-28 21:20:39 ... [blackbox] evaluating batch 10/17 (samples 109..120/204) @ 2024-05-28 21:20:39 ... [blackbox] evaluating batch 11/17 (samples 121..132/204) @ 2024-05-28 21:20:41 ... [blackbox] evaluating batch 12/17 (samples 133..144/204) @ 2024-05-28 21:20:43 ... [blackbox] evaluating batch 13/17 (samples 145..156/204) @ 2024-05-28 21:20:45 ... [blackbox] evaluating batch 14/17 (samples 157..168/204) @ 2024-05-28 21:20:47 ... [blackbox] evaluating batch 15/17 (samples 169..180/204) @ 2024-05-28 21:20:49 ... [blackbox] evaluating batch 16/17 (samples 181..192/204) @ 2024-05-28 21:20:52 ... [blackbox] evaluating batch 17/17 (samples 193..204/204) @ 2024-05-28 21:20:54 ... [blackbox] DONE: see results in output.csv @ 2024-05-28 21:20:57
Clean data¶
In [9]:
Copied!
import pandas as pd
df = pd.read_csv("output.csv")
df.columns = ["x", "y", "z"]
df.x = df.x.astype(int)
df.y = df.y.astype(int)
df
import pandas as pd
df = pd.read_csv("output.csv")
df.columns = ["x", "y", "z"]
df.x = df.x.astype(int)
df.y = df.y.astype(int)
df
Out[9]:
| x | y | z | |
|---|---|---|---|
| 0 | 12 | 24 | 810.98 |
| 1 | 12 | 24 | 810.98 |
| 2 | 15 | 21 | 811.28 |
| 3 | 16 | 19 | 811.58 |
| 4 | 15 | 19 | 811.68 |
| ... | ... | ... | ... |
| 199 | 21 | 11 | 1096.70 |
| 200 | 24 | 10 | 1118.40 |
| 201 | 20 | 15 | 1148.40 |
| 202 | 22 | 13 | 1148.50 |
| 203 | 12 | 11 | 1153.90 |
204 rows × 3 columns
Plot headmap¶
Init Plotly environment¶
In [10]:
Copied!
import plotly.io as pio
pio.renderers.default = "notebook"
pio.templates.default = "plotly_dark"
import plotly.io as pio
pio.renderers.default = "notebook"
pio.templates.default = "plotly_dark"
Type 1¶
In [11]:
Copied!
import plotly.express as px
fig = px.density_contour(
df,
x="x",
y="y",
z="z",
histfunc="max",
)
fig.update_traces(contours_coloring="fill", contours_showlabels=True)
fig.show()
import plotly.express as px
fig = px.density_contour(
df,
x="x",
y="y",
z="z",
histfunc="max",
)
fig.update_traces(contours_coloring="fill", contours_showlabels=True)
fig.show()
Type 2¶
In [27]:
Copied!
import plotly.express as px
fig = px.density_heatmap(
df,
x="x",
y="y",
z="z",
nbinsx=20,
nbinsy=40,
histfunc="max",
color_continuous_scale="Viridis",
)
fig.show()
import plotly.express as px
fig = px.density_heatmap(
df,
x="x",
y="y",
z="z",
nbinsx=20,
nbinsy=40,
histfunc="max",
color_continuous_scale="Viridis",
)
fig.show()
Type 3¶
In [13]:
Copied!
import plotly.graph_objects as go
fig = go.Figure(
go.Histogram2d(
x=df.x,
y=df.y,
z=df.z,
nbinsx=20,
nbinsy=40,
histfunc="max",
)
)
fig.show()
import plotly.graph_objects as go
fig = go.Figure(
go.Histogram2d(
x=df.x,
y=df.y,
z=df.z,
nbinsx=20,
nbinsy=40,
histfunc="max",
)
)
fig.show()
Source¶
--8<-- "example/optimize/blackbox.py"